package com.tyf.bookreader.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.tyf.bookreader.constant.CommonConstants;
import com.tyf.bookreader.domain.*;
import com.tyf.bookreader.dto.*;
import com.tyf.bookreader.manager.BookCacheManager;
import com.tyf.bookreader.manager.BookCategoryCacheManager;
import com.tyf.bookreader.manager.ChapterCacheManager;
import com.tyf.bookreader.manager.ContentCacheManager;
import com.tyf.bookreader.mapper.*;
import com.tyf.bookreader.service.BookService;
import com.tyf.bookreader.component.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.*;

/**
 * @Description TODO
 * @Author shallow
 * @Date 2023/4/2 9:52
 */

@Service
@Slf4j
public class BookServiceImpl implements BookService {

    @Autowired
    private BookCacheManager bookCacheManager;

    @Autowired
    private BookCategoryCacheManager bookCategoryCacheManager;

    @Autowired
    private ContentCacheManager contentCacheManager;

    @Autowired
    private BrCategoryMapper categoryMapper;

    @Autowired
    private ChapterCacheManager chapterCacheManager;
    @Autowired
    private BrBookMapper bookMapper;

    @Autowired
    private BrAuthorMapper authorMapper;

    @Autowired
    private BrChapterMapper chapterMapper;

    @Autowired
    private BrContentMapper contentMapper;

    /**
     * 查看小说分类表
     * @return
     */
    @Override
    public Result<List<BookCategoryDto>> listCategory() {
        return Result.ok(bookCategoryCacheManager.listCategory());
    }

    /**
     * 根据id获取小说信息
     * @param bookId
     * @return
     */
    @Override
    public Result<BookInfoDto> getBookById(Long bookId) {
        return Result.ok(bookCacheManager.getBookById(bookId));
    }

    /**
     * 增加小说阅读量
     * @param bookId
     * @return
     */
    @Override
    public Result addVisitCount(Long bookId) {
        bookCacheManager.addVisitCount(bookId);
        return Result.ok();
    }

    /**
     * 获得某书最新章节信息
     * @param bookId
     * @return
     */
    @Override
    public Result<LastChapterInfoDto> getLastChapterAbout(Long bookId) {
        //查询小说信息
        BookInfoDto bookInfoDto = bookCacheManager.getBookById(bookId);
        //查询最新章节信息
        ChapterDto chapterDto = chapterCacheManager.getChapterById(bookInfoDto.getBookLastedChapter());
        //查询章节内容，并截取前30字作为摘要
        ContentDto contentDto = contentCacheManager.getContentById(chapterDto.getId());

        //查询章节总数
        Integer total = chapterMapper.selectCount(new LambdaQueryWrapper<BrChapter>()
                .eq(BrChapter::getBookId, bookId)
                .eq(BrChapter::getDeleted, 0));
        return Result.ok(LastChapterInfoDto.builder()
                .chapterDto(chapterDto)
                .chapterTotal(total.longValue())
                .contentSummary(contentDto.getContent().substring(0,30)).build());
    }

    /**
     * 小说推荐列表，推荐最近更新的同类别小说
     * @param bookId
     * @return
     */
    @Override
    public Result<List<BookInfoDto>> listRecBooks(Long bookId) throws NoSuchAlgorithmException {
        //获得类别id
        Long categoryId = bookCacheManager.getBookById(bookId).getCategoryId();
        //获得该类最近更新书目id
        List<Long> lastUpdateList = bookCategoryCacheManager.getLastUpdateList(categoryId);
        //封装结果
        ArrayList<BookInfoDto> bookInfoDtoList = new ArrayList<>();
        Random rand = SecureRandom.getInstanceStrong();
        List<Integer> recIdIndexList = new ArrayList<>();
        int count = 0;
        while(count< CommonConstants.REC_BOOK_COUNT){
            int index = rand.nextInt(lastUpdateList.size());
            if(!recIdIndexList.contains(index)){
                recIdIndexList.add(index);
                bookId = lastUpdateList.get(index);
                BookInfoDto bookInfoDto = bookCacheManager.getBookById(bookId);
                bookInfoDtoList.add(bookInfoDto);
                count++;
            }
        }

        return Result.ok(bookInfoDtoList);
    }

    /**
     * 获得本书章节列表
     * @param bookId
     * @return
     */
    @Override
    public Result<List<ChapterDto>> listChapters(Long bookId) {
        List<BrChapter> chapterList = chapterMapper.selectList((new LambdaQueryWrapper<BrChapter>())
                .eq(BrChapter::getBookId, bookId)
                .eq(BrChapter::getDeleted, 0)
                .orderByAsc(BrChapter::getChapterNum));
        return Result.ok(chapterList.stream().map(
                v-> ChapterDto.builder()
                    .id(v.getId())
                    .bookId(v.getBookId())
                    .chapterNum(v.getChapterNum())
                    .chapterName(v.getChapterName())
                    .chapterUpdateTime(v.getUpdateTime()).build()).toList());
    }

    /**
     * 获取本章内容
     * @param chapterId
     * @return
     */
    @Override
    public Result<ContentDto> getContentByChapterId(Long chapterId) {
        //查询本章节信息
        ChapterDto chapterDto = chapterCacheManager.getChapterById(chapterId);
        //获取本章内容
        ContentDto contentDto = contentCacheManager.getContentById(chapterId);
        //获取本书名
        String bookName = bookCacheManager.getBookById(chapterDto.getBookId()).getBookName();
        return Result.ok(ContentDto.builder()
                .bookName(bookName)
                .chapterNum(chapterDto.getChapterNum())
                .content(contentDto.getContent())
                .chapterName(chapterDto.getChapterName())
                .build());
    }

    @Override
    public Result<Long> getPreChapterId(Long chapterId) {
        //查询bookId和章节号chapterNum
        ChapterDto chapterDto = chapterCacheManager.getChapterById(chapterId);
        Long bookId = chapterDto.getBookId();
        Long chapterNum = chapterDto.getChapterNum();
//        查询上一章信息
        BrChapter preChapter = chapterMapper.selectOne(new LambdaQueryWrapper<BrChapter>()
                .eq(BrChapter::getBookId, bookId)
                .lt(BrChapter::getChapterNum, chapterNum)
                .orderByDesc(BrChapter::getChapterNum)
                .last("limit 1"));
        if(Objects.isNull(preChapter)){
            return Result.ok();
        }
        return Result.ok(preChapter.getBookId());
    }

    @Override
    public Result<Long> getNextChapterId(Long chapterId) {
        //查询bookId和章节号chapterNum
        ChapterDto chapterDto = chapterCacheManager.getChapterById(chapterId);
        Long bookId = chapterDto.getBookId();
        Long chapterNum = chapterDto.getChapterNum();
//        查询下一章信息
        Long nextChapterId = chapterMapper.selectOne(new LambdaQueryWrapper<BrChapter>()
                .eq(BrChapter::getBookId, bookId)
                .gt(BrChapter::getChapterNum, chapterNum)
                .orderByAsc(BrChapter::getChapterNum)
                .last("limit 1")).getId();
        return Result.ok(Optional.ofNullable(nextChapterId).orElse(null));
    }

    @Override
    public Result<List<BookDto>> getHotBook() {
        List<BookDto> hotBookList = bookCacheManager.getHotBook();
        return Result.ok(hotBookList);
    }

    @Override
    public Result<ContentDto> getContent(String bookId, String chapterId) {
        return null;
    }

    @Override
    public boolean checkBookPurchase(String bookId) {
        return false;
    }
}
